package buildSchema

import (
	"fmt"
	"os"
	"os/exec"
	"strings"
	"time"

	"gopkg.in/yaml.v3"
)

type ImportResult struct {
	Success      bool                   `json:"success"`
	Message      string                 `json:"message"`
	ImportedRows int                    `json:"imported_rows"`
	FailedRows   int                    `json:"failed_rows"`
	Duration     string                 `json:"duration"`
	Details      map[string]interface{} `json:"details"`
}

// ExecuteImport 执行数据导入
func ExecuteImport(yamlPath, dataPath string) (*ImportResult, error) {
	startTime := time.Now()

	// 验证配置文件
	if err := validateYAMLConfig(yamlPath); err != nil {
		return nil, fmt.Errorf("YAML配置验证失败: %w", err)
	}

	// 更新YAML配置中的数据文件路径
	if err := updateDataPathInYAML(yamlPath, dataPath); err != nil {
		return nil, fmt.Errorf("更新配置文件失败: %w", err)
	}

	// 执行nebula-importer
	result, err := executeNebulaImporter(yamlPath)
	if err != nil {
		return nil, fmt.Errorf("执行导入失败: %w", err)
	}

	result.Duration = time.Since(startTime).String()
	return result, nil
}

// executeNebulaImporter 执行nebula-importer命令
func executeNebulaImporter(yamlPath string) (*ImportResult, error) {
	// 检查nebula-importer是否存在
	importerPath := "config/tool/nebula-importer"
	if _, err := os.Stat(importerPath); os.IsNotExist(err) {
		// 尝试从PATH中查找
		if _, err := exec.LookPath("nebula-importer"); err != nil {
			return nil, fmt.Errorf("nebula-importer工具未找到，请确保已安装")
		}
		importerPath = "nebula-importer"
	}

	// 执行导入命令
	cmd := exec.Command(importerPath, "--config", yamlPath)
	output, err := cmd.CombinedOutput()

	result := &ImportResult{
		Success: err == nil,
		Message: string(output),
		Details: make(map[string]interface{}),
	}

	if err != nil {
		result.Message = fmt.Sprintf("导入失败: %s\n输出: %s", err.Error(), string(output))
		return result, nil
	}

	// 解析输出获取统计信息
	parseImportOutput(string(output), result)

	return result, nil
}

// parseImportOutput 解析导入输出获取统计信息
func parseImportOutput(output string, result *ImportResult) {
	lines := strings.Split(output, "\n")
	for _, line := range lines {
		if strings.Contains(line, "Total") && strings.Contains(line, "rows") {
			// 尝试解析行数统计
			result.Details["output_line"] = line
		}
		if strings.Contains(line, "Success") {
			result.Details["success_info"] = line
		}
		if strings.Contains(line, "Failed") {
			result.Details["failed_info"] = line
		}
	}
}

// validateYAMLConfig 验证YAML配置文件
func validateYAMLConfig(yamlPath string) error {
	data, err := os.ReadFile(yamlPath)
	if err != nil {
		return err
	}

	var config map[string]interface{}
	if err := yaml.Unmarshal(data, &config); err != nil {
		return fmt.Errorf("YAML格式错误: %w", err)
	}

	// 检查必要的配置项
	if _, ok := config["clientSettings"]; !ok {
		return fmt.Errorf("缺少clientSettings配置")
	}

	if _, ok := config["files"]; !ok {
		return fmt.Errorf("缺少files配置")
	}

	return nil
}

// updateDataPathInYAML 更新YAML配置中的数据文件路径
func updateDataPathInYAML(yamlPath, dataPath string) error {
	data, err := os.ReadFile(yamlPath)
	if err != nil {
		return err
	}

	var config map[string]interface{}
	if err := yaml.Unmarshal(data, &config); err != nil {
		return err
	}

	// 更新文件路径
	if files, ok := config["files"].([]interface{}); ok {
		for _, file := range files {
			if fileMap, ok := file.(map[string]interface{}); ok {
				fileMap["path"] = dataPath
				// 设置失败数据路径
				failPath := strings.Replace(dataPath, ".csv", "_fail.csv", 1)
				fileMap["failDataPath"] = failPath
			}
		}
	}

	// 写回文件
	updatedData, err := yaml.Marshal(config)
	if err != nil {
		return err
	}

	return os.WriteFile(yamlPath, updatedData, 0644)
}
